home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
FishMarket 1.0
/
FishMarket v1.0.iso
/
fishies
/
051-075
/
disk_075
/
dum2
/
src
/
dutypefi.mod
< prev
next >
Wrap
Text File
|
1992-05-06
|
7KB
|
271 lines
IMPLEMENTATION MODULE DuTypefile;
(*$S-*)(*$T-*)(*$A+*)
(*
Written by Greg Browne from ideas in duIII.c - many thanks to
Chris Nicotra, Dave Jobusch, Ed Alford, and many others whose
names I have not seen on the source files who have worked on
the development and extension of that fine directory utility program.
PURPOSE A self-contained, IMPORTable pair of procedures to allow
a screen display - or printer copy - in Hex or ASCII of
any disk files.
CHANGES 1/24/87 Built original.
*)
FROM SYSTEM IMPORT ADR;
FROM Strings IMPORT String,InitStringModule,Concat,Assign;
FROM DOSFiles IMPORT FileHandle,ModeOldFile,ModeNewFile,Close,
Open,Read,Write,Lock,Unlock,AccessRead,
FileLock;
FROM DOSLibrary IMPORT DOSName,DOSBase;
FROM Libraries IMPORT OpenLibrary,CloseLibrary;
(*COMMENTS*)
(* This module tries to open the DOSLibrary for use in case it is not open.
IT DOES NOT CLOSE IT. The user is left with that chore. *)
(* All constants and variables are internal. Nothing but PROCEDURES
are available to the user. *)
CONST
lf = 12C;
dot = ".";
cr = 15C;
expl = "q[33m<CR>q[2m = next line - q[33m<SPACE>q[2m = next page - q[33m<ESC>q[2m = abortq[0m";
wipe = "x x";
last ="q[33mEnd of File. Press SPACE q[0m";
VAR
HexCh : ARRAY [0..16] OF CHAR;
Disk,
Display : FileHandle;
fp1,fp2,
fp3,fp4 : CARDINAL;
c : CHAR;
len,len2,
i,
top,
linecount,
nextout : CARDINAL;
Result : LONGINT;
DiskERR,
PastEOF,
KeepWaiting,
OnScreen,
Quit : BOOLEAN;
command : ARRAY[0..79] OF CHAR;
writebuffer : ARRAY[0..80] OF CHAR;
t2 : ARRAY[1..20] OF CHAR;
inbuffer : ARRAY[0..512] OF CHAR;
(* INTERNAL PROCEDURES - NOT IN .def FILE AND NOT IMPORTABLE *)
PROCEDURE MyOpen(VAR ufn:ARRAY OF CHAR):BOOLEAN;
VAR i:CARDINAL;lk:FileLock;
BEGIN
linecount := 0;
Disk := 0;
Quit := FALSE;
lk := Lock(ufn,AccessRead);
IF (lk <> 0) THEN
Unlock(lk);
Disk := Open(ufn,ModeOldFile);
END;
IF Disk = 0 THEN
RETURN FALSE
ELSE
IF OnScreen THEN
Concat("RAW:0/0/640/200/Listing of: ",ufn,command);
ELSE
command := "PRT:"
END;
Display := Open(command,ModeNewFile);
IF Display = 0 THEN
Close(Disk); (* if here - Disk is open *)
RETURN FALSE
ELSE
Quit := FALSE;
RETURN TRUE
END
END
END MyOpen;
(* write a string to 'f' - faster than multiple WriteChar's *)
PROCEDURE WriteString(f:FileHandle;VAR s:ARRAY OF CHAR);
VAR i:CARDINAL;
BEGIN
i := 0;
WHILE (i<=HIGH(s)) AND (s[i]<>0C) DO INC(i) END;
Result := Write(f,ADR(s),LONGCARD(i));
END WriteString;
(* read (with wait) single character from 'f' (here it is keyboard) *)
PROCEDURE ReadChar(f:FileHandle;VAR c:CHAR);
BEGIN
Result := Read(f,ADR(c),1);
IF Result < 1 THEN c := 0C END
END ReadChar;
(* Press Space message and wait for continue-nextline-cancel *)
PROCEDURE Pause;
BEGIN
IF OnScreen THEN
linecount := 1;
WriteString(Display,expl);
KeepWaiting := TRUE;
REPEAT
ReadChar(Display,c);
IF c = CHR(27) THEN
Quit := TRUE;
ELSIF c = CHR(13) THEN
linecount := 21;
END
UNTIL (Quit) OR (c = 15C) OR (c = 40C);
WriteString(Display,wipe);
END;
END Pause;
(* End - press space message & wait for space *)
PROCEDURE Finish;
BEGIN
IF OnScreen THEN
WriteString(Display,last);
REPEAT ReadChar(Display,c) UNTIL (c = 40C);
END;
END Finish;
(* Closes the disk file and screen (or printer) - NOT DOS Library *)
PROCEDURE CloseTheFile;
BEGIN
IF (Display <> 0) THEN Close(Display) END;
IF (Disk <> 0) THEN Close(Disk) END;
END CloseTheFile;
(* internal procedure for the HexDisplay *)
(* Converts a character to a 3 byte (null terminated 3d byte) string *)
(* in hex format with leading '0' *)
PROCEDURE ToHex(c:CHAR;VAR ch:ARRAY OF CHAR);
VAR v:CARDINAL;
BEGIN
v := CARDINAL(ORD(c));
ch[0] := HexCh[v DIV 16];
ch[1] := HexCh[v MOD 16];
ch[2] := 0C;
END ToHex;
(* kludge to quickly convert a 4 byte (artificial LONGCARD) thingy into
an increasing file position - used 4 byte since very big files should
really be taken into account - as if anyone is going to dump a file
that long - oh, well, it will address it properly if they do *)
PROCEDURE HexAddr(VAR ch:ARRAY OF CHAR);
VAR re:ARRAY[0..2] OF CHAR;
BEGIN
IF fp1=256 THEN fp1 := 0; INC(fp2) END; (* with any other *)
IF fp2=256 THEN fp2 := 0; INC(fp3) END; (* necessary movement *)
IF fp3=256 THEN fp3 := 0; INC(fp4) END;
IF fp4=256 THEN fp4 := 0 END; (*if THAT big, just roll*)
ToHex(CHR(fp4),re);
ch[0] := re[0];ch[1] := re[1];
ToHex(CHR(fp3),re);
ch[2] := re[0];ch[3] := re[1];
ToHex(CHR(fp2),re);
ch[4] := re[0];ch[5] := re[1];
ToHex(CHR(fp1),re);
ch[6] := re[0];ch[7] := re[1];
INC(fp1,16);
END HexAddr;
(* FINALLY THE FIRST IMPORTABLE PROCEDURE *)
(* SET ToScreen FALSE to go to PRT: device *)
PROCEDURE DisplayASCII(VAR filnam:ARRAY OF CHAR;ToScreen:BOOLEAN);
BEGIN
OnScreen := ToScreen;
IF MyOpen(filnam) THEN
REPEAT
len := CARDINAL(Read(Disk,ADR(inbuffer),512));
len2 := 0;
WHILE (NOT Quit) AND (len2 < len) DO
i := len2;
WHILE (i < 511) AND (inbuffer[i] <> 12C) DO INC(i) END;
Result := Write(Display,ADR(inbuffer[len2]),LONGCARD(i-len2+1));
len2 := i + 1;
INC(linecount);
IF (linecount > 21) AND (inbuffer[i] = 12C) THEN Pause END;
END;
UNTIL (len <> 512) OR (Quit);
Finish;
END; (* IF NOT Quit *)
CloseTheFile;
END DisplayASCII;
PROCEDURE DisplayHex(VAR filnam:ARRAY OF CHAR;ToScreen:BOOLEAN);
VAR ad:ARRAY[0..7] OF CHAR;
BEGIN
OnScreen := ToScreen;
IF MyOpen(filnam) THEN
fp1:=0;fp2:=0;fp3:=0;fp4:=0;
REPEAT
FOR i := 0 TO 70 DO writebuffer[i] := 40C END;
top := CARDINAL(Read(Disk,ADR(t2),16));
nextout := 10;
IF top > 0 THEN
FOR i := 1 TO top DO
ToHex(t2[i],ad);
writebuffer[nextout] := ad[0];
writebuffer[nextout+1] := ad[1];
INC(nextout,2);
IF (i MOD 4)=0 THEN INC(nextout) END;
END;
nextout := 48; (* 39 IF i MOD 8 is left in *)
FOR i := 1 TO top DO
IF (t2[i]>177C) OR (t2[i]<40C) THEN
writebuffer[nextout] := dot
ELSE
writebuffer[nextout] := t2[i]
END;
INC(nextout);
END;
writebuffer[69] := lf;
writebuffer[70] := 0C;
HexAddr(ad);
FOR i := 0 TO 7 DO writebuffer[i] := ad[i] END;
Result := Write(Display,ADR(writebuffer),70);
INC(linecount);
IF (linecount > 21) THEN Pause END;
END;
UNTIL (top < 16) OR (Quit);
Finish
END;
CloseTheFile
END DisplayHex;
(* Initialization items *)
BEGIN
IF DOSBase = 0 THEN DOSBase := OpenLibrary(DOSName,0) END;
IF DOSBase = 0 THEN HALT END; (* WHOOPS!!*)
InitStringModule;
HexCh := "0123456789ABCDEF";
END DuTypefile.